package com.dd.ent.car.common.player;

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.ObjectAnimator;
import android.content.Context;
import android.graphics.Color;
import android.media.AudioManager;
import android.text.Spannable;
import android.text.SpannableStringBuilder;
import android.text.style.ForegroundColorSpan;
import android.util.AttributeSet;
import android.util.DisplayMetrics;
import android.view.GestureDetector;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.TextView;

import com.dd.ent.car.R;
import com.pp.ent.base.log.MLog;

/**
 * Created by wx on 2016/3/16.
 *
 * @modify LiuJianSheng 2016/04/21
 */
public class MediaPlayerGestureView extends FrameLayout implements MediaPlayerStateChangeListener {
    private static final String TAG = "PlayerGestureView";
    private GestureDetector mGestureDetector;
    private State mState = State.IDLE;
    private float mTouchDownX = -1;
    private float mTouchDownY = -1;

    //进度
    private int mMediaDuration;
    private int mTouchDownPosition;
    private int mCurrentSeekPosition;//移动后的进度
    private float mPixelDuration;//移动一个像素对应的时间
    private View mPositionLayout;
    private ImageView mPositionIcon;
    private ProgressBar mPositionProgressView;
    private TextView mPositionView;

    //音量
    private int mVolumeMax;
    private int mCurrentVolume;
    private AudioManager mAudioManager;
    private View mVolumeLayout;
    private ImageView mVolumeIcon;
    private ProgressBar mVolumeProgressView;

    //亮度
    private ScreenBrightnessTool mScreenLightTool;
    private int mCurrentLight;
    private View mLightLayout;
    private ProgressBar mLightProgressView;

    private boolean mShouldDetectorGestureMove;//是否监听手势滑动

    private OnClickToDetailListener mOnClickToDetailListener;

    private ObjectAnimator mHideAnimator;
    private ObjectAnimator mShowAnimator;

    private ThunderMediaPlayer mMediaPlayer;

    public MediaPlayerGestureView(Context context) {
        super(context);
        initParameters(context);
        initView(context);
    }

    public MediaPlayerGestureView(Context context, AttributeSet attrs) {
        super(context, attrs);
        initParameters(context);
        initView(context);
    }

    public MediaPlayerGestureView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        initParameters(context);
        initView(context);
    }

    private void initView(Context context) {
        LayoutInflater.from(context).inflate(R.layout.thunder_media_player_gesture_view, this, true);

        mPositionLayout = findViewById(R.id.position_layout);
        mPositionView = (TextView) findViewById(R.id.position_view);
        mPositionIcon = (ImageView) findViewById(R.id.position_icon);
        mPositionProgressView = (ProgressBar) findViewById(R.id.position_progress);

        mVolumeLayout = findViewById(R.id.volume_layout);
        mVolumeIcon = (ImageView) findViewById(R.id.volume_icon);
        mVolumeProgressView = (ProgressBar) findViewById(R.id.volume_progress);
        mVolumeProgressView.setMax(mVolumeMax);

        mLightLayout = findViewById(R.id.light_layout);
        mLightProgressView = (ProgressBar) findViewById(R.id.light_progress);
        mLightProgressView.setMax(ScreenBrightnessTool.MAX_BRIGHTNESS);

        mGestureDetector = new GestureDetector(context, mGestureListener);
        mGestureDetector.setIsLongpressEnabled(false);
    }

    private void initParameters(Context context) {
        mAudioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);
        mVolumeMax = mAudioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC);

        mScreenLightTool = ScreenBrightnessTool.Builder(context);
        if (mScreenLightTool != null) {
            mCurrentLight = mScreenLightTool.getSystemBrightness();
        }
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        boolean detectedUp = ((event.getAction() & MotionEvent.ACTION_MASK) == MotionEvent.ACTION_UP);
        if (!mGestureDetector.onTouchEvent(event) && detectedUp) {
            return onTouchUp(event);
        }
        return true;
    }

    public void bindMediaPlayer(ThunderMediaPlayer mediaPlayer) {
        this.mMediaPlayer = mediaPlayer;
    }

    public void setMediaDuration(int duration) {
        this.mMediaDuration = duration;
        mPixelDuration = (float) duration / getWidth();
        mPositionProgressView.setMax(duration);
    }

    private void setTouchDownPosition(int touchDownPosition) {
        this.mTouchDownPosition = touchDownPosition;
    }

    public void setShouldDetectorGestureMove(boolean shouldDetectorGestureMove) {
        this.mShouldDetectorGestureMove = shouldDetectorGestureMove;
    }

    private boolean onTouchUp(MotionEvent e) {
        MLog.debug(TAG, "onTouchUp--mState=" + mState);
        MLog.debug(TAG, "animationToResetState--mState=" + mState);
        switch (mState) {
            case IDLE:
                if (mOnClickToDetailListener == null) {
                    mMediaPlayer.getControllerView().toggle();
                } else {
                    mOnClickToDetailListener.onClick();
                }
                break;
            case POSITION:
                if (mMediaDuration > 0) {
                    startHideAnimation(mPositionLayout);
                    mMediaPlayer.safetySeekTo(mCurrentSeekPosition);
                }
                break;
            case VOLUME:
                startHideAnimation(mVolumeLayout);
                updateCurrentVolume();
                break;
            case LIGHT:
                startHideAnimation(mLightLayout);
                updateCurrentLight();
                break;
        }
        mState = State.IDLE;
        return true;
    }

    private GestureDetector.OnGestureListener mGestureListener = new GestureDetector.SimpleOnGestureListener() {
        @Override
        public boolean onDown(MotionEvent e) {
            mTouchDownX = e.getRawX();
            mTouchDownY = e.getRawY();
            if (mMediaPlayer != null) {
                int currentPos = mMediaPlayer.getCurrentPosition();
                if (currentPos >= 0) {
                    setTouchDownPosition(currentPos);
                }
            }
            MLog.debug(TAG, "onDown--mState=" + mState + "|X=" + mTouchDownX + "|Y=" + mTouchDownY);
            return true;
        }

        @Override
        public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
            if (!mShouldDetectorGestureMove) {
                return true;
            }
            float touchDownX = mTouchDownX;
            float touchDownY = mTouchDownY;
            if (!canAdjustOnTouch(touchDownX, touchDownY)) {
                return true;
            }
            int distanceDownX = (int) (e2.getX() - touchDownX);
            int distanceDownY = (int) (e2.getY() - touchDownY);
//            MLog.debug(TAG, "onScroll--distanceX=" + distanceX + "|distanceY=" + distanceY + "distanceDownX=" + distanceDownX + "|distanceDownY=" + distanceDownY);
            switch (mState) {
                case IDLE:
                    if (Math.abs(distanceX) > Math.abs(distanceY)) {//左右拖动
                        enterPositionState(distanceDownX);
                    } else if (touchDownX > getWidth() / 2) {//右边上下拖动
                        enterVolumeState();
                    } else {//左边上下拖动
                        enterLightState();
                    }
                    break;
                case POSITION:
                    if (mMediaDuration <= 0) {
                        return true;
                    }
                    int distanceProgress = (int) (distanceDownX * mPixelDuration);
                    int seekPosition = mTouchDownPosition + distanceProgress;
                    if (seekPosition < 0) {
                        seekPosition = 0;
                    } else if (seekPosition > mMediaDuration) {
                        seekPosition = mMediaDuration;
                    }
                    updatePositionIcon(distanceDownX);
                    setSeekPositionText(seekPosition, mMediaDuration);
                    mPositionProgressView.setProgress(seekPosition);
                    mCurrentSeekPosition = seekPosition;
                    break;
                case VOLUME:
                    if (mVolumeMax > 0) {
                        int distanceVolume = -(distanceDownY * mVolumeMax / getHeight());
                        int newVolume = mCurrentVolume + distanceVolume;
                        if (newVolume < 0) {
                            newVolume = 0;
                        } else if (newVolume > mVolumeMax) {
                            newVolume = mVolumeMax;
                        }
                        updateVolumeIcon(newVolume);
                        mVolumeProgressView.setProgress(newVolume);
                        mAudioManager.setStreamVolume(AudioManager.STREAM_MUSIC, newVolume, AudioManager.FLAG_REMOVE_SOUND_AND_VIBRATE);
                    }
                    break;
                case LIGHT:
                    if (mScreenLightTool != null) {
                        int distanceLight = -(distanceDownY * ScreenBrightnessTool.MAX_BRIGHTNESS / getHeight());
                        int newLight = mCurrentLight + distanceLight;
                        if (newLight < 0) {
                            newLight = 0;
                        } else if (newLight > ScreenBrightnessTool.MAX_BRIGHTNESS) {
                            newLight = ScreenBrightnessTool.MAX_BRIGHTNESS;
                        }
                        mLightProgressView.setProgress(newLight);
                        mScreenLightTool.setBrightness(newLight);
                    }
                    break;
            }
            return true;
        }

    };

    private boolean canAdjustOnTouch(float touchDownX, float touchDownY) {
        DisplayMetrics dm = getResources().getDisplayMetrics();
        int exceptPixel = 50;//touchDown时，屏幕最外围的像素不做处理，用户可能是想下拉通知栏
        int screenWidth = dm.widthPixels;
        int screenHeight = dm.heightPixels;
        if (touchDownX < exceptPixel || touchDownX > screenWidth - exceptPixel || touchDownY < exceptPixel || touchDownY > screenHeight - exceptPixel) {
            return false;
        }
        return true;
    }

    private void updatePositionIcon(int distanceDownX) {
        if (distanceDownX < 0) {
            mPositionIcon.setImageResource(R.drawable.player_gesture_go_back_icon);
        } else {
            mPositionIcon.setImageResource(R.drawable.player_gesture_go_forward_icon);
        }
    }

    private void setSeekPositionText(int seekPosition, int mediaDuration) {
        String seekPositionStr = StringUtil.formatDuration(seekPosition);
        String mediaDurationStr = StringUtil.formatDuration(mediaDuration);
        String wholeStr = seekPositionStr + " / " + mediaDurationStr;
        SpannableStringBuilder style = new SpannableStringBuilder(wholeStr);
        int start = wholeStr.indexOf(seekPositionStr);
        style.setSpan(new ForegroundColorSpan(Color.parseColor("#1294f6")), start, start + seekPositionStr.length(), Spannable.SPAN_EXCLUSIVE_INCLUSIVE);
        mPositionView.setText(style);
    }

    private void updateVolumeIcon(int volume) {
        if (volume == 0) {
            mVolumeIcon.setImageResource(R.drawable.player_gesture_silent_icon);
        } else {
            mVolumeIcon.setImageResource(R.drawable.player_gesture_volume_icon);
        }
    }

    private void enterPositionState(int distanceDownX) {
        MLog.debug(TAG, "enterPositionState--distanceDownX=" + distanceDownX);
        mState = State.POSITION;
        if (mMediaDuration > 0) {
            mMediaPlayer.getControllerView().hide();
            updatePositionIcon(distanceDownX);
            mPositionLayout.setAlpha(1);
            showStateLayout(mPositionLayout);
        }
    }

    private void enterLightState() {
        MLog.debug(TAG, "enterLightState--");
        mMediaPlayer.getControllerView().hide();
        mState = State.LIGHT;
        mLightLayout.setAlpha(1);
        showStateLayout(mLightLayout);
    }

    private void enterVolumeState() {
        MLog.debug(TAG, "enterVolumeState--");
        mMediaPlayer.getControllerView().hide();
        mState = State.VOLUME;
        updateVolumeIcon(mCurrentVolume);
        mVolumeLayout.setAlpha(1);
        showStateLayout(mVolumeLayout);
    }

    private void updateCurrentVolume() {
        mCurrentVolume = mAudioManager.getStreamVolume(AudioManager.STREAM_MUSIC);
    }

    private void updateCurrentLight() {
        if (mScreenLightTool != null) {
            mCurrentLight = mScreenLightTool.getSystemBrightness();
        }
    }

    @Override
    public void onStateChange(MediaPlayerState oldState, MediaPlayerState newState) {
        switch (newState) {
            case PREPARED:
//                setMediaDuration(mMediaPlayer.getDuration());
                break;
            case IDLE:
                resetStateToIdle();
                break;
        }
    }

    enum State {
        IDLE,//初始状态
        POSITION,//调节播放进度
        VOLUME,//调节音量
        LIGHT,//调节亮度
    }

    private void showStateLayout(final View layout) {
        MLog.debug(TAG, "showStateLayout--layout=" + layout);
        if (mHideAnimator != null) {
            mHideAnimator.cancel();
            mHideAnimator = null;
        }
        ObjectAnimator showAnimator = ObjectAnimator.ofFloat(layout, View.ALPHA, 1);
        showAnimator.setDuration(200);
        layout.setVisibility(View.VISIBLE);
        showAnimator.start();
        mShowAnimator = showAnimator;
    }

    private void startHideAnimation(final View layout) {
        MLog.debug(TAG, "startHideAnimation--layout=" + layout);
        if (mShowAnimator != null) {
            mShowAnimator.cancel();
            mShowAnimator = null;
        }
        ObjectAnimator hideAnimator = ObjectAnimator.ofFloat(layout, View.ALPHA, 0);
        hideAnimator.setDuration(500);
        hideAnimator.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                layout.setVisibility(View.GONE);
            }
        });
        hideAnimator.start();
        mHideAnimator = hideAnimator;
    }

    public void resetStateToIdle() {
        mState = State.IDLE;
        mLightLayout.setVisibility(View.GONE);
        mVolumeLayout.setVisibility(View.GONE);
        mPositionLayout.setVisibility(View.GONE);
    }

    public void setClickToDetailListener(OnClickToDetailListener onClickToDetailListener) {
        mOnClickToDetailListener = onClickToDetailListener;
    }

    public interface OnClickToDetailListener {
        void onClick();
    }
}
